﻿namespace EasyGo.Logic.Managers
{
    using System;
    using System.Linq;
    using System.Security;

    using EasyGo.Common;
    using EasyGo.Common.Commands;
    using EasyGo.Logic.Model;

    public class UsersManager : IUsersManager
    {
        private readonly IRepository<User> userRepository;

        public UsersManager(IRepository<User> userRepository)
        {
            this.userRepository = userRepository;
        }

        public void CreateUser(EditUserCommand command)
        {
            var loweredEmail = command.Email.ToLower();
            command.Validate();
            var emailNotUnique = this.userRepository.GetAll().Any(x => x.Email == loweredEmail);
            if (emailNotUnique)
            {
                throw new SecurityException("Email not unique");
            }

            var newUser = new User();
            this.MapCommandToUser(newUser, command);
            newUser.AddDate = DateTime.Now;
            newUser.Password = command.Password;
            newUser.Email = loweredEmail;
            
            Transaction.Execute(() => this.userRepository.Create(newUser));
        }

        public void EditUser(EditUserCommand command)
        {
            command.Validate();
            Transaction.Execute(
                () =>
                    {
                        var toEdit = this.userRepository.Load(command.Id);
                        if (toEdit != null)
                        {
                            this.MapCommandToUser(toEdit, command);
                            if (!string.IsNullOrEmpty(command.Password))
                            {
                                toEdit.Password = command.Password;
                            }

                            this.userRepository.Update(toEdit);
                        }
                    });
        }

        public void DeleteUser(int id)
        {
            Transaction.Execute(() =>
                { 
                    var toDelete = this.userRepository.Load(id);
                    this.userRepository.Delete(toDelete);
                    this.userRepository.SaveChanges();
                });
        }

        private void MapCommandToUser(User user, EditUserCommand command)
        {
            user.FirstName = command.FirstName;
            user.LastName = command.LastName;
            user.Description = command.Description;
            user.IsEnabled = true;
            user.Role = command.Role;
        }
    }
}